/**
 * 兼容forEach
 * @param iterate ArrayLike
 * @param callback function
 * @param thisArg this
 */
export function forEach(iterate, callback, thisArg) {
  [].forEach.call(iterate, callback, thisArg);
}

/**
 * 为没有includes方法的ArrayLike对象提供includes
 * @param iterate ArrayLike
 * @param valueToFind Any
 * @param fromIndex Number
 * @return Boolean
 */
export function includes(iterate, valueToFind, fromIndex) {
  return [].includes.call(iterate, valueToFind, fromIndex);
}

/**
 * 防抖函数
 * @param fn function
 * @param delayTime number
 */
export function debounce(fn, delayTime) {
  let debounceTimer = null;
  return function(...args) {
    let _this = this;
    if (debounceTimer) {
      clearTimeout(debounceTimer);
    }
    debounceTimer = setTimeout(() => {
      fn && fn.apply(_this, args);
    }, delayTime);
  };
}

/**
 * 节流函数
 * @param fn function
 * @param delayTime number
 */
export function throttle(fn, delayTime) {
  let throttleTimer = null;
  let throttleLastTime = null;
  return function(...args) {
    let _this = this;
    if (throttleLastTime && throttleLastTime + delayTime > Date.now()) {
      clearTimeout(throttleTimer);
      throttleTimer = setTimeout(() => {
        fn && fn.apply(_this, args);
      }, delayTime);
    } else {
      fn && fn.apply(_this, args);
      throttleLastTime = Date.now();
    }
  };
}

/**
 * json数组根据字段去重
 * @param {Array} arr
 * @param {String} key
 * @returns {Array}
 * */
export function uniqBy(arr, key) {
  let tempMap = new Map();
  return arr.reduce((lastVal, item) => {
    if (!tempMap.get(item[key])) {
      tempMap.set(item[key], true);
      lastVal.push(item);
    } else {
      let index = lastVal.findIndex(({ [key]: value }) => value === item[key]);
      lastVal[index] = item;
    }
    return lastVal;
  }, []);
}
